#include "ContactListener.h"
#include "Object/Object.h"
#include "Object/Ball.h"
#include "Object/Bucket.h"


CContactListener::CContactListener()
{
	_contacts.clear();
}


CContactListener::~CContactListener()
{
}

void CContactListener::BeginContact(b2Contact *contact)
{
	// We need to copy out the data because the b2Contact passed in
	// is reused.
	CContact myContact = { contact->GetFixtureA(), contact->GetFixtureB() };
	_contacts.push_back(myContact);
}


void CContactListener::EndContact(b2Contact* contact) {
	CContact myContact = { contact->GetFixtureA(), contact->GetFixtureB() };
	std::vector<CContact>::iterator pos;
	pos = std::find(_contacts.begin(), _contacts.end(), myContact);
	if (pos != _contacts.end()) {

		//wcg
		//handle collision
		this->HandleCollision(myContact);
		//end
		_contacts.erase(pos);
	}
}

void CContactListener::PreSolve(b2Contact* contact, const b2Manifold* oldManifold) {
}

void CContactListener::PostSolve(b2Contact* contact, const b2ContactImpulse* impulse) {
}


void CContactListener::HandleCollision(CContact &myContact)
{
	void* obj1 = myContact.fixtureA->GetBody()->GetUserData();
	void* obj2 = myContact.fixtureB->GetBody()->GetUserData();
	if(obj1 && obj2)
	{
		CObject* firstObj = (CObject*)obj1;
		CObject* secondObj = (CObject*)obj2;

		//collision:  ball and bucket
		if ((firstObj->getTag() == kBallTag && secondObj->getTag() == kBucketTag) ||
			(firstObj->getTag() == kBucketTag && secondObj->getTag() == kBallTag) )
		{
			//get the ball speed
			b2Vec2 ballSpeed;
			CBall* ballObj;
			CBucket* bucketObj;


			if (firstObj->GetObjectClassification() == ObjectClassification_Ball)
			{
				ballObj = (CBall*) firstObj;
				bucketObj = (CBucket*)secondObj;
				ballSpeed = myContact.fixtureA->GetBody()->GetLinearVelocity();
			}
			else if(secondObj->GetObjectClassification() == ObjectClassification_Ball)
			{
				ballObj = (CBall*) secondObj;
				bucketObj = (CBucket*)firstObj;
				ballSpeed = myContact.fixtureB->GetBody()->GetLinearVelocity();
			}
			//
			if (fabs(ballSpeed.x) <kStillSpeed && fabs(ballSpeed.y) < kStillSpeed)
			{
				//the same color
				if (firstObj->GetObjectColorType() ==  secondObj->GetObjectColorType())
				{
					ballObj->BingoInBucket();
				}
				else if(BallShootByBucket != ballObj->GetBallState())
				{
					ballObj->ShootByBucket(bucketObj);
				}
			}
		}
	}
}